package com.luxsoft.sw3.contabilidad.ui;

import java.text.DateFormat;
import java.text.MessageFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang.time.DateUtils;
import org.apache.log4j.Logger;

import ca.odell.glazedlists.BasicEventList;
import ca.odell.glazedlists.EventList;
import ca.odell.glazedlists.GlazedLists;
import ca.odell.glazedlists.UniqueList;

import com.luxsoft.siipap.cxc.model.Aplicacion;
import com.luxsoft.siipap.cxc.model.AplicacionDePago;
import com.luxsoft.siipap.cxc.model.Pago;
import com.luxsoft.siipap.cxc.model.PagoConCheque;
import com.luxsoft.siipap.cxc.model.PagoConDeposito;
import com.luxsoft.siipap.cxc.model.PagoConEfectivo;
import com.luxsoft.siipap.cxc.model.PagoConTarjeta;
import com.luxsoft.siipap.cxc.model.PagoDeDiferencias;
import com.luxsoft.siipap.model.CantidadMonetaria;
import com.luxsoft.siipap.model.Sucursal;
import com.luxsoft.siipap.model.contabilidad.AsientoContable;
import com.luxsoft.siipap.model.contabilidad.Poliza;
import com.luxsoft.siipap.service.ServiceLocator2;
import com.luxsoft.siipap.util.DateUtil;
import com.luxsoft.siipap.util.MonedasUtils;
import com.luxsoft.siipap.ventas.model.Venta;

/**
 * Genera la poliza de ventas tipo cobranza camioneta
 * 
 * Tipo de informacion:
 * 
 * CUENTA CONCEPTO DEBE HABER COBRANZA 102-EFEC-000 SCOTTIA X 102-CHEQ-000
 * SCOTTIA X 102-TDEB-000 BANAMEX X 102-TCRE-000 BANAMEX X 102-TAMX-000
 * BANAMEX-AMX X 102-DEPO-000 VARIOS X
 * 
 * 6SUC-0020-000 COMISIONES BANCARIAS Suc CAM X 117-0001-003 I.V.A. EN GASTOS X
 * 6SUC-0020-000 COMISIONES BANCARIAS CRE X 117-0001-003 I.V.A. EN GASTOS X
 * 
 * 203-D002-000 Pg Tar(CRE) Fac:docto CLTE X 206-0002-001 I.V.A. Pend/Pg:Tarj
 * CRE Suc X
 * 
 * 105-0Suc-000 Pg Tar(CAM) Fac:docto CLAVE X 206-0002-001 I.V.A. Pend/Pg:Tarj
 * CAM Suc X 206-0001-001 I.V.A. en Ventas CAM Suc X
 * 
 * 902-0002-000 ACUMULABLE IETU CAM X 903-0002-000 ACUMULABLE IETU CAM X
 * 
 * 204-D001-000 ANT A CLIENTES X 206-0001-005 IVA ANT A CLIENTES X
 * 
 * 203-D001-000 ACREEDORES DIVERSOS 0
 * 
 * 110-B003-000 FUNCIONARIOS EMPLEADOS 0
 * 
 * 704-0001-000 OTROS GASTOS CAM X
 * 
 * 702-0001-000 OTROS INGRESOS CAM X
 * 
 * 
 * 
 * Anticipos
 * 
 * </#list> 206-0001-001 , 0 IVA ventas CAM
 * 
 * ${ivaEnVentas?c},1.00
 * 
 * 206-0001-001 , 0 IVA ventas CAM X Ant
 * 
 * ${ivaEnVentasAnticipos?c},1.00
 * 
 * 206-0002-001 , 0 IVA en ventas pend ${ivaEnVentas?c},1.00
 * 
 * 206-0002-001 , 0 IVA en ventas pend x ant ${ivaEnVentasAnticipos?c},1.00
 * 
 * 204-D001-000 , 0 ANTICIPOS DE CLIENTES ${anticipos?c},1.00
 * 
 * 206-0001-005 , 0 IVA EN ANTI CLIENTES ${ivaAnticipos?c},1.00
 * 
 * DEVOLUCIONES
 * 
 * 405-0003-${sucursal} , 0 DEVOLUCIONES SOBRE VENTAS ${devoluciones?c},1.00
 * 
 * 206-0002-002 , 0 IVA EN DEVO PEND X TRASLADAR
 * ${ivaEnDevPendienteTrasladar?c},1.00
 * 
 * 
 * COBRANZA 105-0${sucursal}-000 , 0 CLIENTES CAM ${sucursalName}
 * 
 * ${clientesPagos?c},1.00
 * 
 * 
 * TARJETA
 * 
 * 203-D001-000 , 0 ACREDORES PAG TARJETA ${acredores?c},1.00
 * 
 * OTROS
 * 
 * 702-0001-000 , 0 OTROS INGRESOS DIVERSOS
 * 
 * ${otrosIngresosDiversos?c},1.00
 * 
 * 702-0005-000 , 0 OTROS INGRESOS SALDO FAVOR
 * 
 * ${otrosIngresosSaldoAFavor?c},1.00
 * 
 * 206-0001-001 , 0 IVA EN COB. OTROS ING
 * 
 * ${ivaOtrosIngresos?c},1.00
 * 
 * 206-0002-001 , 0 IVA PEND EN COB. OTROS ING ${ivaOtrosIngresos?c},1.00
 * 
 * 
 * 
 * 
 * @author Ruben Cancino Ramos
 * 
 */
public class PolizaDeCobranzaCamionetaController {

protected Logger logger=Logger.getLogger(getClass());
	
	private DateFormat df=new SimpleDateFormat("dd-MM-yy");
	
	private EventList<Pago> pagos;
	private EventList<Aplicacion> aplicaciones;
	private EventList<Aplicacion> saldosAFavor;
	
	/**
	 * Genera las polizas de ventas mostrador para la fecha indicada
	 * una por cada sucursal
	 * 
	 * @param fecha
	 * @return
	 */
	public List<Poliza> generarPoliza(final Date fecha ){		
		List<Poliza> res=new ArrayList<Poliza>();
		List<Sucursal> sucursales=ServiceLocator2
				.getLookupManager()
				.getSucursalesOperativas();
		
		for(Sucursal s:sucursales){
			try {
				Poliza p=generar(fecha, s);
				p.depurar();
				p.ordenNatural();
				res.add(p);
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
		return res;
	}
	
	private Poliza generar(final Date dia,final Sucursal suc){
		
		final Poliza pol=new Poliza();
		pol.setConcepto("Cobranza camioneta "+df.format(dia)+" "+suc.getNombre());
		pol.setFecha(dia);
		pol.setFolio(0);
		pol.setTipo("Dr");
		pol.setSucursalId(suc.getClaveContable());
		pol.setSucursalNombre(suc.getNombre());
		registrarBancos(pol,suc);
		registrarAbonoAClientesCamioneta(pol,suc);
		registrarAnticipos(pol, suc);
		registrarAnticiposAplicados(pol, suc);
		registrarAplicacionDeSaldosAFavor(pol, suc);		
		registrarSaldosAFavor(pol, suc);
		registrarIETU(pol, suc);
		registrarOtrosIngresosGastos(pol, suc);
		return pol;
	}	
	
	
	//private void prepararPago
	
	private void registrarBancos(final Poliza poliza,final  Sucursal suc){
		
		pagos=new UniqueList<Pago>(new BasicEventList<Pago>(),GlazedLists.beanPropertyComparator(Pago.class, "id"));
		aplicaciones=new BasicEventList<Aplicacion>();
		saldosAFavor=new BasicEventList<Aplicacion>();
		Date fecha=poliza.getFecha();
		String hql="from Aplicacion a where a.fecha=? and a.cargo.sucursal.id=? " +
				" and a.cargo.origen=\'CAM\'";
		List<AplicacionDePago> aplicaciones=ServiceLocator2
			.getHibernateTemplate().find(hql,new Object[]{fecha,suc.getId()});
		for(Aplicacion ap:aplicaciones){
			
			if(!(ap.getAbono() instanceof Pago))
				continue;
			//Excluir Pagos con tarjeta
			if(ap.getAbono() instanceof PagoConTarjeta)
				continue;
			if(ap.getAbono() instanceof PagoDeDiferencias)
				continue;
			Date fechaAplicacion=ap.getFecha();
			Date fechaPrimeraAplicacion=ap.getAbono().getPrimeraAplicacion();
			Pago pago=(Pago)ap.getAbono();
			if(DateUtils.isSameDay(fechaAplicacion, fechaPrimeraAplicacion)){
				this.aplicaciones.add(ap);
				if(!pago.isAnticipo())
					pagos.add(pago);
			}else{
				if(!pago.isAnticipo())
					saldosAFavor.add(ap);
				continue;
				
			}
				
		}
		
		String concepto="Cob cam "+df.format(poliza.getFecha())+suc.getNombre();
		concepto=StringUtils.substring(concepto, 0, 27);
		
		//Pagos en efectivo
		
		CantidadMonetaria totalEfectivo=CantidadMonetaria.pesos(0);
		for(Pago p:pagos){
			if(p instanceof PagoConEfectivo){
				System.out.println("Acumulando pago: "+p+ "Por: "+p.getTotal()+ ""+p.getFecha()+ "Fol: "+p.getFolio());
				totalEfectivo=totalEfectivo.add(p.getTotalCM());
			}
		}
		AsientoContable asientoEfectivo=new AsientoContable();
		asientoEfectivo.setCuenta("102-0001-000");
		asientoEfectivo.setConcepto(concepto);
		asientoEfectivo.setAgrupador("A");
		asientoEfectivo.setDebe(totalEfectivo);
		asientoEfectivo.setDescripcion("Efectivo");
		asientoEfectivo.setDescripcion2("");
		asientoEfectivo.setDescripcion3("");
		asientoEfectivo.setSucursal(suc.getNombre());
		asientoEfectivo.setTipo("D");
		//poliza.agregarAsiento(asientoEfectivo); DBG
		
		//Cheque
		//Pagos en efectivo
		CantidadMonetaria totalCheque=CantidadMonetaria.pesos(0);
		for(Pago p:pagos){
			if(p instanceof PagoConCheque){
				totalCheque=totalCheque.add(p.getTotalCM());
			}
		}
		AsientoContable asientoCheque=new AsientoContable();
		asientoCheque.setCuenta("102-0001-000");
		//concepto="BBVA BANCOMER SA CHEQUE";
		//concepto=StringUtils.substring(concepto, 0, 27);
		asientoCheque.setConcepto(concepto);
		asientoCheque.setAgrupador("A");
		asientoCheque.setDebe(totalCheque);
		asientoCheque.setDescripcion("Cheque");
		asientoCheque.setDescripcion2("");
		asientoCheque.setDescripcion3("");
		asientoCheque.setSucursal(suc.getNombre());
		asientoCheque.setTipo("D");
		//poliza.agregarAsiento(asientoCheque); DBG
		
		
		//Depositos
		List<AsientoContable> asientosSinOrden=new ArrayList<AsientoContable>();
		for(Pago p:pagos){
			
			if(p instanceof PagoConDeposito){
				PagoConDeposito deposito=(PagoConDeposito)p;
				
				if(deposito.getCuenta()!=null){
					AsientoContable asientoDeposito=new AsientoContable();				
					asientoDeposito.setCuenta(deposito.getCuenta().getCuentaContable());
					concepto="Cob cam "+df.format(poliza.getFecha());
					concepto=StringUtils.substring(concepto, 0, 27);
					asientoDeposito.setConcepto(concepto);
					asientoDeposito.setAgrupador("A");
					asientoDeposito.setDebe(deposito.getTotalCM());
					asientoDeposito.setDescripcion("Depositos");
					asientoDeposito.setDescripcion2("");
					asientoDeposito.setDescripcion3("");
					asientoDeposito.setSucursal(suc.getNombre());
					asientoDeposito.setTipo("D");					
					//asientosSinOrden.add(asientoDeposito);
					
				}
				
			}
			
		}
		Collections.sort(asientosSinOrden,new Comparator<AsientoContable>(){
			public int compare(AsientoContable o1, AsientoContable o2) {
				String c1=o1.getCuenta();
				String c2=o2.getCuenta();
				int res=c1.compareTo(c2);
				//System.out.println("Comparando: "+c1+ " con "+c2+ " Res: "+res);
				return res;
			}
		});
		for(AsientoContable a:asientosSinOrden){
			poliza.agregarAsiento(a);
		}
		
	}
		
	private void registrarAbonoAClientesCamioneta(final Poliza poliza,final Sucursal suc){
		
		CantidadMonetaria importe=CantidadMonetaria.pesos(0);
		
		for(Aplicacion a:this.aplicaciones){
			Pago pago=(Pago)a.getAbono();
			if(pago.isAnticipo())
				continue;
			CantidadMonetaria total=a.getImporteCM();
			importe=importe.add(total);
		}
		
		AsientoContable a=new AsientoContable();
		String cuenta="105-"+suc.getClaveContableAsString()+"-000";
		a.setCuenta(cuenta);
		a.setHaber(importe);
		a.setConcepto("Pago Camioneta");
		a.setSucursal(suc.getNombre());
		a.setDescripcion(suc.getNombre());
		a.setAgrupador("A");
		a.setTipo("H");
		poliza.agregarAsiento(a);
		
	}
	
	private void registrarAnticipos(final Poliza poliza,final Sucursal suc){
		
		CantidadMonetaria importe=CantidadMonetaria.pesos(0);
		CantidadMonetaria impuesto=CantidadMonetaria.pesos(0);
		CantidadMonetaria totalIntergrafics=CantidadMonetaria.pesos(0);
		
		List<Pago> anticipos=ServiceLocator2.getHibernateTemplate().find(
				"from Pago p where p.fecha=? " +
				" and p.anticipo=true " +
				" and p.origen!=\'CRE\'" +
				" and p.sucursal.id=?"
				,new Object[]{poliza.getFecha(),suc.getId()});
		
		for(Pago pago:anticipos){
			if(pago.isAnticipo()){				
				if(pago.getClave().equals("I010406")){
					totalIntergrafics=totalIntergrafics.add(pago.getTotalCM());
					continue;
				}
				CantidadMonetaria total=pago.getImporteCM();
				CantidadMonetaria imp=MonedasUtils.calcularImporteDelTotal(total);
				CantidadMonetaria iva=MonedasUtils.calcularImpuesto(imp);
				importe=importe.add(imp);
				impuesto=impuesto.add(iva);				
			}
		}
		
		AsientoContable a=new AsientoContable();
		String cuenta="204-D001-000";
		a.setCuenta(cuenta);
		a.setHaber(importe);
		a.setConcepto("Anticipos camioneta");
		a.setSucursal(suc.getNombre());
		a.setDescripcion(suc.getNombre());
		a.setAgrupador("A");
		a.setTipo("H");
		poliza.agregarAsiento(a);
		
		AsientoContable a2=new AsientoContable();
		a2.setCuenta("206-0003-005");
		a2.setHaber(impuesto);
		a2.setConcepto("IVA en Anticipos");
		a2.setSucursal(suc.getNombre());
		a2.setDescripcion(suc.getNombre());
		a2.setAgrupador("A");
		a2.setTipo("H");
		poliza.agregarAsiento(a2);
		
		if(totalIntergrafics.amount().doubleValue()>0){
			CantidadMonetaria importeEspecial=MonedasUtils.calcularImporteDelTotal(totalIntergrafics);
			CantidadMonetaria impuestoEspecial=MonedasUtils.calcularImpuesto(importeEspecial);
			AsientoContable especial=new AsientoContable();
			especial.setCuenta("204-I007-000");
			especial.setHaber(MonedasUtils.calcularImporteDelTotal(totalIntergrafics));
			especial.setConcepto("Anticipos camioneta");
			especial.setSucursal(suc.getNombre());
			especial.setDescripcion(suc.getNombre());
			especial.setAgrupador("A");
			especial.setTipo("H");
			poliza.agregarAsiento(especial);
			
			AsientoContable especialIVA=new AsientoContable();
			especialIVA.setCuenta("206-0003-005");
			especialIVA.setHaber(impuestoEspecial);
			especialIVA.setConcepto("IVA en Anticipos");
			especialIVA.setSucursal(suc.getNombre());
			especialIVA.setDescripcion(suc.getNombre());
			especialIVA.setAgrupador("A");
			especialIVA.setTipo("H");
			poliza.agregarAsiento(especialIVA);
			
		}
		
		//Afectacion a bancos de los anticipos
		CantidadMonetaria totalEfectivo=CantidadMonetaria.pesos(0);
		CantidadMonetaria totalCheque=CantidadMonetaria.pesos(0);
		for(Pago p:anticipos){
			if(p instanceof PagoConEfectivo){
				totalEfectivo=totalEfectivo.add(p.getTotalCM());
			}else if(p instanceof PagoConCheque){
				totalCheque=totalCheque.add(p.getTotalCM());
			}
		}
		
		//Pagos en efectivo
		AsientoContable asientoEfectivo=new AsientoContable();
		asientoEfectivo.setCuenta("102-0001-000");
		String concepto="BBVA BANCOMER SA Efectivo";
		concepto=StringUtils.substring(concepto, 0, 27);
		asientoEfectivo.setConcepto(concepto);
		asientoEfectivo.setAgrupador("A");
		asientoEfectivo.setDebe(totalEfectivo);
		asientoEfectivo.setDescripcion("Efectivo");
		asientoEfectivo.setDescripcion2("");
		asientoEfectivo.setDescripcion3("");
		asientoEfectivo.setSucursal(suc.getNombre());
		asientoEfectivo.setTipo("D");
		//poliza.agregarAsiento(asientoEfectivo); DBG
		
		//Cheque
		AsientoContable asientoCheque=new AsientoContable();
		asientoCheque.setCuenta("102-0001-000");
		concepto="BBVA BANCOMER SA Efectivo";
		concepto=StringUtils.substring(concepto, 0, 27);
		asientoCheque.setConcepto(concepto);
		asientoCheque.setAgrupador("A");
		asientoCheque.setDebe(totalCheque);
		asientoCheque.setDescripcion("Cheque");
		asientoCheque.setDescripcion2("");
		asientoCheque.setDescripcion3("");
		asientoCheque.setSucursal(suc.getNombre());
		asientoCheque.setTipo("D");
		//poliza.agregarAsiento(asientoCheque);DBG
		
		
		//Depositos
		for(Pago p:anticipos){
			if(p instanceof PagoConDeposito){
				PagoConDeposito deposito=(PagoConDeposito)p;
				if(deposito.getCuenta()!=null){
					AsientoContable asientoDeposito=new AsientoContable();				
					asientoDeposito.setCuenta(deposito.getCuenta().getCuentaContable());
					concepto=deposito.getCuenta().getBanco().getClave();
					concepto=StringUtils.substring(concepto, 0, 27);
					asientoDeposito.setConcepto(concepto);
					asientoDeposito.setAgrupador("A");
					asientoDeposito.setDebe(deposito.getTotalCM());
					asientoDeposito.setDescripcion("Depositos");
					asientoDeposito.setDescripcion2("");
					asientoDeposito.setDescripcion3("");
					asientoDeposito.setSucursal(suc.getNombre());
					asientoDeposito.setTipo("D");
					//poliza.agregarAsiento(asientoDeposito);
				}
			}
		}
		
		
		//Cargo a bancos
		CantidadMonetaria totalAnticiposChequeEfectivo=CantidadMonetaria.pesos(0);
		
		for(Pago pago:anticipos){
			if(pago.isAnticipo()){
				if(pago instanceof PagoConDeposito){
					PagoConDeposito deposito=(PagoConDeposito)pago;
					if(deposito.getCuenta()!=null){
						AsientoContable asientoDeposito=new AsientoContable();				
						asientoDeposito.setCuenta(deposito.getCuenta().getCuentaContable());
						concepto=deposito.getCuenta().getBanco().getClave();
						concepto=StringUtils.substring(concepto, 0, 27);
						asientoDeposito.setConcepto(concepto);
						asientoDeposito.setAgrupador("A");
						asientoDeposito.setDebe(deposito.getTotalCM());
						asientoDeposito.setDescripcion("Depositos");
						asientoDeposito.setDescripcion2("");
						asientoDeposito.setDescripcion3("");
						asientoDeposito.setSucursal(suc.getNombre());
						asientoDeposito.setTipo("D");
						//poliza.agregarAsiento(asientoDeposito);
					}
				}else{
					totalAnticiposChequeEfectivo=totalAnticiposChequeEfectivo.add(pago.getTotalCM());
				}								
			}
		}
		AsientoContable cargoABancoTotalEfectivoCheque=new AsientoContable();				
		cargoABancoTotalEfectivoCheque.setCuenta("102-0001-000");
		concepto=StringUtils.substring(concepto, 0, 27);
		cargoABancoTotalEfectivoCheque.setConcepto(concepto);
		cargoABancoTotalEfectivoCheque.setAgrupador("A");
		cargoABancoTotalEfectivoCheque.setDebe(totalAnticiposChequeEfectivo);
		cargoABancoTotalEfectivoCheque.setDescripcion("Anticipo");
		cargoABancoTotalEfectivoCheque.setSucursal(suc.getNombre());
		cargoABancoTotalEfectivoCheque.setTipo("D");
		//poliza.agregarAsiento(cargoABancoTotalEfectivoCheque); DBG
	}
	
	private void registrarAnticiposAplicados(final Poliza poliza,final Sucursal suc){
		
		CantidadMonetaria importe=CantidadMonetaria.pesos(0);
		CantidadMonetaria impIntergrafics=CantidadMonetaria.pesos(0);
		CantidadMonetaria ivaAnticipoAplicado=CantidadMonetaria.pesos(0);
		
	 
		for(Aplicacion a:this.aplicaciones){
			Pago pago=(Pago)a.getAbono();
			if(pago.isAnticipo()){
				CantidadMonetaria imp=MonedasUtils.calcularImporteDelTotal(a.getImporteCM());
				ivaAnticipoAplicado=ivaAnticipoAplicado.add(MonedasUtils.calcularImpuesto(imp));
				if(pago.getClave().equals("I010406")){
					impIntergrafics=impIntergrafics.add(imp);
				}else
					importe=importe.add(imp);
							
			}
		}
		
		AsientoContable a=new AsientoContable();
		String cuenta="204-D001-000";
		a.setCuenta(cuenta);
		a.setDebe(importe);
		a.setConcepto("Aplic Anticipos camioneta");
		a.setSucursal(suc.getNombre());
		a.setDescripcion(suc.getNombre());
		a.setAgrupador("T");
		a.setTipo("D");
		poliza.agregarAsiento(a);
		
		
		AsientoContable a10=new AsientoContable();
		String cuenta1="105-"+suc.getClaveContableAsString()+"-000";
		a10.setCuenta(cuenta1);
		a10.setHaber(MonedasUtils.calcularTotal(importe));
		a10.setConcepto("Aplic Anticipos camioneta");
		a10.setSucursal(suc.getNombre());
		a10.setDescripcion(suc.getNombre());
		a10.setAgrupador("T");
		a10.setTipo("H");
		poliza.agregarAsiento(a10);
				
						
		if(impIntergrafics.amount().doubleValue()>0){
			
			AsientoContable especial=new AsientoContable();
			especial.setCuenta("204-I007-000");
			especial.setDebe(impIntergrafics);
			especial.setConcepto("Aplic Anticipos camioneta");
			especial.setSucursal(suc.getNombre());
			especial.setDescripcion(suc.getNombre());
			especial.setAgrupador("T");
			especial.setTipo("D");
			poliza.agregarAsiento(especial);
			
			AsientoContable a20=new AsientoContable();
			String cuenta2="105-"+suc.getClaveContableAsString()+"-000";
			a20.setCuenta(cuenta2);
			a20.setHaber(MonedasUtils.calcularTotal(impIntergrafics));
			a20.setConcepto("Aplic Anticipos camioneta");
			a20.setSucursal(suc.getNombre());
			a20.setDescripcion(suc.getNombre());
			a20.setAgrupador("T");
			a20.setTipo("H");
			poliza.agregarAsiento(a20);
			
			
			
						
		}
		
		/**** Iva ****/
		AsientoContable iva=new AsientoContable();
		iva.setCuenta("206-0003-005");
		iva.setDebe(ivaAnticipoAplicado);
		iva.setConcepto("IVA en Anticipos");
		iva.setSucursal(suc.getNombre());
		iva.setDescripcion(suc.getNombre());
		iva.setAgrupador("T");
		iva.setTipo("D");
		poliza.agregarAsiento(iva);
		
		/** Traspaso de IVA ***/
		
		AsientoContable iva1=new AsientoContable();
		iva1.setCuenta("206-0003-001");
		iva1.setHaber(ivaAnticipoAplicado);
		iva1.setConcepto("IVA Traspa X Anticipo ");
		iva1.setSucursal(suc.getNombre());
		iva1.setDescripcion(suc.getNombre());
		iva1.setAgrupador("T");
		iva1.setTipo("H");
		poliza.agregarAsiento(iva1);
		
		AsientoContable iva2=new AsientoContable();
		iva2.setCuenta("206-0004-001");
		iva2.setDebe(ivaAnticipoAplicado);
		iva2.setConcepto("IVA Traspa X Ant Cte");
		iva2.setSucursal(suc.getNombre());
		iva2.setDescripcion(suc.getNombre());
		iva2.setAgrupador("T");
		iva2.setTipo("D");
		poliza.agregarAsiento(iva2);
		
		
	}
	
	private void registrarAplicacionDeSaldosAFavor(final Poliza pol,final Sucursal suc){
		
		CantidadMonetaria saldoAFavor=CantidadMonetaria.pesos(0);
		
		for(Aplicacion a:saldosAFavor){
			saldoAFavor=saldoAFavor.add(a.getImporteCM());			
		}		
		AsientoContable asientoCheque=new AsientoContable();
		asientoCheque.setCuenta("203-D003-000");
		String concepto="Aplic de saldo a favor";
		concepto=StringUtils.substring(concepto, 0, 27);
		asientoCheque.setConcepto(concepto);
		asientoCheque.setDebe(saldoAFavor);
		asientoCheque.setDescripcion("");
		asientoCheque.setSucursal(suc.getNombre());
		asientoCheque.setTipo("D");
		asientoCheque.setAgrupador("F");
		pol.agregarAsiento(asientoCheque);
		
		AsientoContable haber=new AsientoContable();
		String cuenta="105-"+suc.getClaveContableAsString()+"-000";
		haber.setCuenta(cuenta);
		concepto=StringUtils.substring(concepto, 0, 27);
		haber.setConcepto(concepto);
		haber.setHaber(saldoAFavor);
		haber.setDescripcion("");
		haber.setSucursal(suc.getNombre());
		haber.setTipo("H");
		haber.setAgrupador("F");
		pol.agregarAsiento(haber);
		
		CantidadMonetaria importeSaldoAFAvor=MonedasUtils.calcularImporteDelTotal(saldoAFavor);
		CantidadMonetaria impuestoSaldoAFavor=MonedasUtils.calcularImpuesto(importeSaldoAFAvor);
		
		AsientoContable ivaEnVentas=new AsientoContable();
		ivaEnVentas.setCuenta("206-0004-001");
		ivaEnVentas.setDebe(impuestoSaldoAFavor);
		ivaEnVentas.setConcepto("IVA en Ventas pend. por tras");
		ivaEnVentas.setSucursal(suc.getNombre());
		ivaEnVentas.setDescripcion(suc.getNombre());
		ivaEnVentas.setAgrupador("X");
		ivaEnVentas.setTipo("D");
		pol.agregarAsiento(ivaEnVentas);
		
		AsientoContable ivaEnVentas2=new AsientoContable();
		ivaEnVentas2.setCuenta("206-0003-001");
		ivaEnVentas2.setHaber(impuestoSaldoAFavor);
		ivaEnVentas2.setConcepto("IVA en Ventas cobr CAM");
		ivaEnVentas2.setSucursal(suc.getNombre());
		ivaEnVentas2.setDescripcion(suc.getNombre());
		ivaEnVentas2.setAgrupador("X");
		ivaEnVentas2.setTipo("H");
		pol.agregarAsiento(ivaEnVentas2);
		
	}
	
	private void registrarSaldosAFavor(final Poliza pol,final Sucursal suc){
		
		
		CantidadMonetaria saldoAFavor=CantidadMonetaria.pesos(0);		
		
		for(Pago pago:this.pagos){
			pago=(Pago)ServiceLocator2.getCXCManager().getAbono(pago.getId());
			CantidadMonetaria disponible=pago.getDisponibleAlCorte(pol.getFecha());
			if(disponible.amount().doubleValue()>0){
				if(DateUtils.isSameDay(pago.getPrimeraAplicacion(),pol.getFecha())){
					saldoAFavor=saldoAFavor.add(disponible);
				}
			}			
		}
		
		AsientoContable asientoCheque=new AsientoContable();
		asientoCheque.setCuenta("203-D003-000");
		String concepto="Saldo a Favor";
		concepto=StringUtils.substring(concepto, 0, 27);
		asientoCheque.setConcepto(concepto);		
		asientoCheque.setHaber(saldoAFavor);
		asientoCheque.setDescripcion("");
		asientoCheque.setSucursal(suc.getNombre());
		asientoCheque.setTipo("H");
		asientoCheque.setAgrupador("A");
		pol.agregarAsiento(asientoCheque);
		
		CantidadMonetaria iva=MonedasUtils.calcularImporteDelTotal(saldoAFavor.abs().multiply(-1));
		iva=MonedasUtils.calcularImpuesto(iva);
		AsientoContable ivaEnVentas=new AsientoContable();
		ivaEnVentas.setCuenta("206-0004-001");
		ivaEnVentas.setDebe(iva);
		ivaEnVentas.setConcepto("IVA en Ventas pend. por tras");
		ivaEnVentas.setSucursal(suc.getNombre());
		ivaEnVentas.setDescripcion(suc.getNombre());
		ivaEnVentas.setAgrupador("X");
		ivaEnVentas.setTipo("D");
		pol.agregarAsiento(ivaEnVentas);
		
		AsientoContable ivaEnVentas2=new AsientoContable();
		ivaEnVentas2.setCuenta("206-0003-001");
		ivaEnVentas2.setHaber(iva);
		ivaEnVentas2.setConcepto("IVA en Ventas cobr CAM");
		ivaEnVentas2.setSucursal(suc.getNombre());
		ivaEnVentas2.setDescripcion(suc.getNombre());
		ivaEnVentas2.setAgrupador("X");
		ivaEnVentas2.setTipo("H");
		pol.agregarAsiento(ivaEnVentas2);
		
	}
	
	private void registrarIETU(final Poliza poliza, final Sucursal suc){
		
		AsientoContable a1=new AsientoContable();
		a1.setConcepto("ACUMULABLE IETU (CAM)");
		a1.setCuenta("902-0002-000");
		
		AsientoContable a2=new AsientoContable();
		a2.setConcepto("IETU ACUMULABLE (CAM)");
		a2.setCuenta("903-0002-000");
		
		CantidadMonetaria importePagos=CantidadMonetaria.pesos(0);
		CantidadMonetaria importeAnticipos=CantidadMonetaria.pesos(0);
		
		for(Pago p:pagos){
			if(p instanceof PagoDeDiferencias)
				continue;
			if(p.isAnticipo()){
				importeAnticipos=importeAnticipos.add(p.getImporteCM());
			}else
				importePagos=importePagos.add(p.getImporteCM());
		}
		
		CantidadMonetaria importeIetu=importePagos.subtract(importeAnticipos);
		
		a1.setDebe(importeIetu);
		a1.setAgrupador("X");
		a2.setHaber(importeIetu);
		a2.setAgrupador("X");
		poliza.getRegistros().add(a1);
		poliza.getRegistros().add(a2);
		
		AsientoContable ivaEnVentas=new AsientoContable();
		ivaEnVentas.setCuenta("206-0004-001");
		ivaEnVentas.setDebe(MonedasUtils.calcularImpuesto(importeIetu));
		ivaEnVentas.setConcepto("IVA en Ventas pend. por tras");
		ivaEnVentas.setSucursal(suc.getNombre());
		ivaEnVentas.setDescripcion(suc.getNombre());
		ivaEnVentas.setAgrupador("X");
		ivaEnVentas.setTipo("D");
		poliza.agregarAsiento(ivaEnVentas);
		
		AsientoContable ivaEnVentas2=new AsientoContable();
		ivaEnVentas2.setCuenta("206-0003-001");
		ivaEnVentas2.setHaber(MonedasUtils.calcularImpuesto(importeIetu));
		ivaEnVentas2.setConcepto("IVA en Ventas cobr CAM");
		ivaEnVentas2.setSucursal(suc.getNombre());
		ivaEnVentas2.setDescripcion(suc.getNombre());
		ivaEnVentas2.setAgrupador("X");
		ivaEnVentas2.setTipo("H");
		poliza.agregarAsiento(ivaEnVentas2);
		
		
		AsientoContable ietuAnticipoCargo=new AsientoContable();
		ietuAnticipoCargo.setCuenta("902-0002-000");
		ietuAnticipoCargo.setDebe(importeAnticipos);
		ietuAnticipoCargo.setConcepto("IETU Anticipo");
		ietuAnticipoCargo.setSucursal(suc.getNombre());
		ietuAnticipoCargo.setDescripcion(suc.getNombre());
		ietuAnticipoCargo.setAgrupador("X");
		ietuAnticipoCargo.setTipo("D");
		poliza.agregarAsiento(ietuAnticipoCargo);
		
		AsientoContable ietuAnticipoAbono=new AsientoContable();
		ietuAnticipoAbono.setCuenta("903-0002-000");
		ietuAnticipoAbono.setHaber(importeAnticipos);
		ietuAnticipoAbono.setConcepto("IETU Anticipo");
		ietuAnticipoAbono.setSucursal(suc.getNombre());
		ietuAnticipoAbono.setDescripcion(suc.getNombre());
		ietuAnticipoAbono.setAgrupador("X");
		ietuAnticipoAbono.setTipo("H");
		poliza.agregarAsiento(ietuAnticipoAbono);
		
		/// IETU DE ANTICIPOS de lo aplicado
		CantidadMonetaria totalAnticipos=CantidadMonetaria.pesos(0);
		for(Aplicacion a:aplicaciones){
			Pago p=(Pago)a.getAbono();
			if(p.isAnticipo())
				totalAnticipos=totalAnticipos.add(a.getImporteCM());
		}
		CantidadMonetaria importeIetuAnticiposAplicados=MonedasUtils.calcularImporteDelTotal(totalAnticipos);
	
		AsientoContable ietuAnticipoAplicado_1=new AsientoContable();
		ietuAnticipoAplicado_1.setCuenta("902-0002-000");
		ietuAnticipoAplicado_1.setDebe(importeIetuAnticiposAplicados);
		ietuAnticipoAplicado_1.setConcepto("IETU Reg An");
		ietuAnticipoAplicado_1.setSucursal(suc.getNombre());
		ietuAnticipoAplicado_1.setDescripcion(suc.getNombre());
		ietuAnticipoAplicado_1.setAgrupador("X");
		ietuAnticipoAplicado_1.setTipo("D");
		poliza.agregarAsiento(ietuAnticipoAplicado_1);
		
		AsientoContable ietuAnticipoAplicado_2=new AsientoContable();
		ietuAnticipoAplicado_2.setCuenta("903-0002-000");
		ietuAnticipoAplicado_2.setHaber(importeIetuAnticiposAplicados);
		ietuAnticipoAplicado_2.setConcepto("IETU Reg Ant");
		ietuAnticipoAplicado_2.setSucursal(suc.getNombre());
		ietuAnticipoAplicado_2.setDescripcion(suc.getNombre());
		ietuAnticipoAplicado_2.setAgrupador("X");
		ietuAnticipoAplicado_2.setTipo("H");
		poliza.agregarAsiento(ietuAnticipoAplicado_2);
		
		AsientoContable ietuAnticipoAplicado_3=new AsientoContable();
		ietuAnticipoAplicado_3.setCuenta("902-0006-000");
		ietuAnticipoAplicado_3.setDebe(importeIetuAnticiposAplicados.multiply(-1));
		ietuAnticipoAplicado_3.setConcepto("IETU Sal Reg Ant");
		ietuAnticipoAplicado_3.setSucursal(suc.getNombre());
		ietuAnticipoAplicado_3.setDescripcion(suc.getNombre());
		ietuAnticipoAplicado_3.setAgrupador("X");
		ietuAnticipoAplicado_3.setTipo("D");
		poliza.agregarAsiento(ietuAnticipoAplicado_3);
		
		AsientoContable ietuAnticipoAplicado_4=new AsientoContable();
		ietuAnticipoAplicado_4.setCuenta("903-0006-000");
		ietuAnticipoAplicado_4.setHaber(importeIetuAnticiposAplicados.multiply(-1));
		ietuAnticipoAplicado_4.setConcepto("IETU Sal Reg Ant");
		ietuAnticipoAplicado_4.setSucursal(suc.getNombre());
		ietuAnticipoAplicado_4.setDescripcion(suc.getNombre());
		ietuAnticipoAplicado_4.setAgrupador("X");
		ietuAnticipoAplicado_4.setTipo("H");
		poliza.agregarAsiento(ietuAnticipoAplicado_4);
		
	}
	
	/**
	 *  704-0001-000	OTROS GASTOS MOS		X	
		702-0001-000	OTROS INGRESOS MOS				X
	 * @param poliza
	 * @param suc
	 */
	private void registrarOtrosIngresosGastos(final Poliza poliza,final Sucursal suc){
		
		//Otros ingresos
		CantidadMonetaria otrosIngresos=CantidadMonetaria.pesos(0);
		for(Pago pago:pagos){
			CantidadMonetaria diferencia=new CantidadMonetaria(pago.getDiferencia(),pago.getMoneda());
			otrosIngresos=otrosIngresos.add(diferencia);
		}
		
		//Otros gastos
		CantidadMonetaria otrosGastos=CantidadMonetaria.pesos(0);
		for(Pago pago:pagos){
			if(pago instanceof PagoDeDiferencias){
				otrosGastos=otrosGastos.add(pago.getTotalCM());
			}
		}
		
		CantidadMonetaria otros=otrosIngresos.subtract(otrosGastos);
		
		AsientoContable registro1=new AsientoContable();
		registro1.setAgrupador("O");
		registro1.setDescripcion("");
		registro1.setCuenta("702-0001-000");
		registro1.setConcepto("OTROS INGRESOS CAM");
		registro1.setHaber(otros);
		poliza.getRegistros().add(registro1);
		
		AsientoContable registro2=new AsientoContable();
		registro2.setDescripcion("");
		registro2.setAgrupador("O");
		registro2.setCuenta("704-0001-000");
		registro2.setConcepto("OTROS GASTOS CAM");
		registro2.setDebe(otros);
		poliza.getRegistros().add(registro2);
		
	}

	public static void main(String[] args) {
		PolizaDeCobranzaCamionetaController controller=new PolizaDeCobranzaCamionetaController();
		Sucursal suc=(Sucursal)ServiceLocator2
			.getUniversalDao().get(Sucursal.class, 6L);
		Poliza pol=controller.generar(DateUtil.toDate("01/03/2010"), suc);
		for(AsientoContable a:pol.getRegistros()){
			System.out.println(a);
		}
	}
	
}
